package com.example.deepseek.service.impl;

import com.example.deepseek.service.FileService;
import lombok.extern.slf4j.Slf4j;
import org.apache.pdfbox.pdmodel.PDDocument;
import org.apache.pdfbox.text.PDFTextStripper;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;
import org.springframework.web.multipart.MultipartFile;

import java.io.File;
import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.util.ArrayList;
import java.util.List;
import java.util.UUID;

/**
 * 文件服务实现类
 */
@Service
@Slf4j
public class FileServiceImpl implements FileService {

    @Value("${file.upload.directory:./uploads}")
    private String uploadDirectory;

    // 新增：文本分割块大小配置
    @Value("${pdf.chunk.size:400}")
    private int chunkSize;

    @Value("${pdf.chunk.overlap:40}")
    private int chunkOverlap;

    @Override
    public String storeFile(MultipartFile file) throws IOException {
        // 创建上传目录
        File uploadDir = new File(uploadDirectory);
        if (!uploadDir.exists()) {
            uploadDir.mkdirs();
        }

        // 生成唯一文件名
        String originalFilename = file.getOriginalFilename();
        String fileExtension = "";
        if (originalFilename != null && originalFilename.contains(".")) {
            fileExtension = originalFilename.substring(originalFilename.lastIndexOf("."));
        }
        String filename = UUID.randomUUID().toString() + fileExtension;

        // 保存文件
        Path filePath = Paths.get(uploadDirectory, filename);
        Files.copy(file.getInputStream(), filePath);

        return filePath.toString();
    }

    // 在FileServiceImpl.java中添加调试日志
    @Override
    public String readFileContent(String filePath) throws IOException {
        String content;
        if (filePath.toLowerCase().endsWith(".pdf")) {
            content = extractTextFromPdf(filePath);
            log.info("从PDF提取的文本长度: {} 字符, 文件路径: {}", content.length(), filePath);
            // 记录前100个字符作为预览
            if (content.length() > 0) {
                log.info("文本预览: {}", content.substring(0, Math.min(100, content.length())));
            }
        } else {
            content = new String(Files.readAllBytes(Paths.get(filePath)));
            log.info("从普通文件读取的文本长度: {} 字符", content.length());
        }
        return content;
    }

    // 改进PDF文本提取，确保所有文本被正确提取
    private String extractTextFromPdf(String filePath) throws IOException {
        try (PDDocument document = PDDocument.load(new File(filePath))) {
            PDFTextStripper stripper = new PDFTextStripper();
            // 确保按正确的阅读顺序提取
            stripper.setSortByPosition(true);
            String text = stripper.getText(document);

            // 如果提取的文本很短，可能是PDF有特殊格式，尝试其他提取策略
            if (text.length() < 100 && document.getNumberOfPages() > 1) {
                StringBuilder builder = new StringBuilder();
                // 逐页提取
                for (int i = 0; i < document.getNumberOfPages(); i++) {
                    stripper.setStartPage(i + 1);
                    stripper.setEndPage(i + 1);
                    String pageText = stripper.getText(document);
                    builder.append(pageText).append("\n\n--- 第").append(i + 1).append("页 ---\n\n");
                }
                text = builder.toString();
                log.info("使用逐页提取策略，提取了 {} 页内容", document.getNumberOfPages());
            }

            return text;
        } catch (Exception e) {
            log.error("PDF文本提取失败", e);
            return "PDF文本提取失败: " + e.getMessage();
        }
    }

    // 新增：文本分块方法
    public List<String> splitTextIntoChunks(String text) {
        List<String> chunks = new ArrayList<>();

        // 使用递归分割策略
        String[] paragraphs = text.split("\\n\\n");
        StringBuilder currentChunk = new StringBuilder();

        for (String paragraph : paragraphs) {
            // 如果当前段落加上当前块超过了块大小，保存当前块并开始新块
            if (currentChunk.length() + paragraph.length() > chunkSize) {
                // 如果当前块不为空，保存它
                if (currentChunk.length() > 0) {
                    chunks.add(currentChunk.toString());

                    // 保留部分重叠内容
                    String[] words = currentChunk.toString().split("\\s+");
                    if (words.length > chunkOverlap / 10) {
                        currentChunk = new StringBuilder();
                        for (int i = words.length - chunkOverlap / 10; i < words.length; i++) {
                            currentChunk.append(words[i]).append(" ");
                        }
                    } else {
                        currentChunk = new StringBuilder();
                    }
                }
            }

            // 添加段落到当前块
            currentChunk.append(paragraph).append("\n\n");

            // 如果当前块已经超过块大小，强制保存
            if (currentChunk.length() >= chunkSize) {
                chunks.add(currentChunk.toString());
                currentChunk = new StringBuilder();
            }
        }

        // 添加最后一个块，如果不为空
        if (currentChunk.length() > 0) {
            chunks.add(currentChunk.toString());
        }

        return chunks;
    }

    @Override
    public boolean deleteFile(String filePath) {
        try {
            return Files.deleteIfExists(Paths.get(filePath));
        } catch (IOException e) {
            return false;
        }
    }

}